﻿namespace HuwmanCode.Diagnostics.Logging

open System
open System.IO
open System.Globalization
open System.Transactions
open System.Runtime.Serialization
open System.Reflection
open HuwmanCode
open HuwmanCode.IO
open HuwmanCode.Transactions
open HuwmanCode.Diagnostics

/// <summary>
/// The file event writer
/// </summary>
type public FileEventWriter(logFile:string) = 
    interface ILogWriter with
        /// <summary>
        /// Writes to the event trace
        /// </summary>
        member this.Write (message:TraceMessage) =
            let dir = Path.GetDirectoryName(logFile)
            let logFilePath = if dir <> String.Empty then logFile else Path.combineMany [Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);logFile]
            use writer = new StreamWriter(logFile, true)
            
            let msgEntry = sprintf "\"%s\"|\"%A\"|\"%s\"|\"%s\"" (message.Timestamp.ToLongTimeString()) message.Level message.ExecutableName message.Message
            let exnEntry = message.ExceptionDetail
                           |> Seq.fromGraph(fun ed -> ed.InnerException)
                           |> Seq.map(fun ed -> sprintf "\"%s\"|\"%s\"|\"%s\"|\"%s\"|\"%s\"|\"%s\"|\"%i\"" ed.Message ed.Name ed.MethodName ed.TypeName ed.AssemblyName ed.FileName ed.LineNumber)
                           |> Seq.toArray

            writer.WriteLine(msgEntry)
            if exnEntry.Length > 0 then writer.WriteLine(exnEntry |> String.join writer.NewLine)

    interface IDisposable with
        member this.Dispose () =
            ()